package com.pilgrim.generator.vo;

import com.alibaba.fastjson.annotation.JSONField;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonInclude;
import lombok.Data;
import org.springframework.http.HttpStatus;

/**
 * 响应结果对象
 *
 * @author wangyibin
 * @version 1.0.0
 */
@JsonInclude(JsonInclude.Include.NON_NULL)
@Data
public class ResultVO<T> {
    @JsonIgnore
    @JSONField(serialize = false)
    private HttpStatus httpStatus;

    private Integer status;

    private String msg;

    private String error;

    private T data;

    public static <T> ResultVO<T> success() {
        return new ResultVO<T>();
    }

    /**
     * 构建业务处理成功Result
     * HttpStatus=200
     *
     * @param data 响应内容
     * @param <T>  响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> success(T data) {
        return new ResultVO<T>(data);
    }

    /**
     * 构建业务处理成功Result
     * HttpStatus=200
     *
     * @param data 响应内容
     * @param <T>  响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> success(T data, String msg) {
        return new ResultVO<T>(data, msg);
    }

    /**
     * 构建请求参数错误Result
     * HttpStatus=400
     *
     * @param message 错误原因
     * @param <T>     响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> badRequest(String message) {
        return new ResultVO(message, null, HttpStatus.BAD_REQUEST.value());
    }

    /**
     * 构建服务端处理失败或异常Result
     * HttpStatus=500
     *
     * @param message 失败原因
     * @param <T>     响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> fail(String message) {
        return new ResultVO(message, null, HttpStatus.OK.value());
    }

    /**
     * 构建服务端处理失败或异常Result
     * HttpStatus=500
     *
     * @param message 失败原因
     * @param error   java异常信息
     * @param <T>     响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> fail(String message, String error) {
        return new ResultVO(message, error, HttpStatus.OK.value());
    }

    /**
     * 构建指定httpstatus的Result
     *
     * @param message    提示信息
     * @param httpStatus httpstatus
     * @param <T>        响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> status(String message, HttpStatus httpStatus) {
        return new ResultVO(message, null, httpStatus);
    }

    /**
     * 构建指定httpstatus的Result
     *
     * @param message    失败原因
     * @param error      java异常信息
     * @param httpStatus httpstatus
     * @param <T>        响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> status(String message, String error, HttpStatus httpStatus) {
        return new ResultVO(message, error, httpStatus);
    }

    /**
     * 构建指定httpstatus的Result
     *
     * @param message 失败原因
     * @param error   java异常信息
     * @param status  status
     * @param <T>     响应对象
     * @return ResultVO
     */
    public static <T> ResultVO<T> status(String message, String error, int status) {
        return new ResultVO(message, error, status);
    }

    /**
     * 创建响应result对象
     */
    private ResultVO() {
        this.setStatus(HttpStatus.OK.value());
        this.setHttpStatus(HttpStatus.OK);
    }

    /**
     * 创建响应result对象
     *
     * @param data 数据对象
     */
    private ResultVO(T data) {
        this.setStatus(HttpStatus.OK.value());
        this.setHttpStatus(HttpStatus.OK);
        this.setData(data);
    }

    /**
     * 创建响应result对象
     *
     * @param data 数据对象
     */
    private ResultVO(T data, String msg) {
        this.setStatus(HttpStatus.OK.value());
        this.setHttpStatus(HttpStatus.OK);
        this.setData(data);
        this.setMsg(msg);
    }

    /**
     * 创建响应失败result对象
     *
     * @param message 失败原因描述
     * @param error   抛出异常信息
     * @param status  status
     */
    private ResultVO(String message, String error, int status) {
        this.setMsg(message);
        this.setError(error);
        this.setStatus(Integer.valueOf(status));
        this.setHttpStatus(HttpStatus.OK);
    }

    /**
     * 创建响应失败result对象
     *
     * @param message    失败原因描述
     * @param error      抛出异常信息
     * @param httpStatus HttpStatus
     */
    private ResultVO(String message, String error, HttpStatus httpStatus) {
        this.setMsg(message);
        this.setError(error);
        this.setStatus(httpStatus.value());
        this.setHttpStatus(httpStatus);
    }

}
